package com.service.tcp;


import com.domain.Contents;
import com.domain.Equip_data;
import com.domain.Tcp_public_data;
import com.service.Public_funtion;
import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
import io.netty.util.CharsetUtil;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

import static com.MysqlApplication.equip_list;
import static com.MysqlApplication.global_data;

@Service
public class Tcp_public_funtion
{

    @Autowired
    private Public_funtion p;



    public void send_data (ChannelHandlerContext ctx,char[] data)
    {
        char[] send_char=data;
        ctx.channel().writeAndFlush(String.valueOf(send_char)).syncUninterruptibly();
        p.print_log("向"+ctx.channel().remoteAddress().toString()+"发送送数据成功",7);

    }

    public Tcp_public_data tcp_to_object(byte[] getHex)
    {
        Tcp_public_data data= new Tcp_public_data();
        int turn=0;
        String str_data="";
        int length1,length2,length3,length4;
        long length5,length6;


        data.setHead(0x5555);
        turn=getHex[2];//批次1
        data.setBatch(turn);
        length1=(getHex[3]&0xff)<<8;
        length2=getHex[4]&0xff;
        turn=length1+length2;//种类，2
        data.setKind(turn);
        turn=getHex[5];//开关1
        data.setOpen(turn);
        length1=(getHex[6]&0xff)<<8;
        length2=getHex[7]&0xff;
        turn=length1+length2;//速度2
        data.setSpeed(turn);
        length6=((long)getHex[8]&0xff)<<40;
        length5=((long)getHex[9]&0xff)<<32;
        length4=(getHex[10]&0xff)<<24;
        length3=(getHex[11]&0xff)<<16;
        length2=(getHex[12]&0xff)<<8;
        length1=getHex[13]&0xff;
        data.setClour(length1+length2+length3+length4+length5+length6);
        length1=(getHex[14]&0xff)<<8;
        length2=getHex[15]&0xff;
        turn=length1+length2;//长度2
        data.setLenth(turn);

        data.content=new  byte[turn];
        System.arraycopy(getHex,16,data.content,0,turn);



        length1=(getHex[16+turn]&0xff)<<8;
        length2=getHex[17+turn]&0xff;
        turn=length1+length2;//长度2
        data.setCheck(turn);

        data.setTail(0x1314);//长度2
        return data;
    }

    public byte[] json_to_tcp (Tcp_public_data scd)
    {
        int setHexLen=-1;
        byte[] getHex = scd.content;
        if(getHex!=null)
        {
            setHexLen=getHex.length;                          ////发来的数据转成char格式后的长度，作为数组中的长度码
        }
        else {
            setHexLen=0;
        }
        byte[] setHex= new byte[20+setHexLen];           //所有的字符长度，包括检查码和尾码
        int check_num=0;                                //检查码加起来的int数字
        setHex[0]=0x55;setHex[1]=0x55;
        setHex[2]=(byte)scd.getBatch();                 //版本
        setHex[3]=(byte)(scd.getKind()>>8);setHex[4]=(byte)scd.getKind();;  //解码格式
        setHex[5]=(byte)scd.getOpen();
        setHex[6]=(byte)(scd.getSpeed()>>8);setHex[7]=(byte)scd.getSpeed();
        setHex[8]=(byte)(scd.getClour()>>40);setHex[9]=(byte)(scd.getClour()>>32);setHex[10]=(byte)(scd.getClour()>>24);
        setHex[11]=(byte)(scd.getClour()>>16);setHex[12]=(byte)(scd.getClour()>>8);setHex[13]=(byte)scd.getClour();//解码格式
        setHex[14]=(byte)(setHexLen>>8);setHex[15]=(byte)(setHexLen&0xff);
//        System.arraycopy(getHex,0,setHex,16,setHexLen);
for (int i=0;i<setHexLen;i++)
{
    setHex[16+i]=getHex[i];
}
        int i;
        for( i=2;i<16+setHexLen;i++){
            check_num +=((int)setHex[i]&0xff);
        }
        byte[] check_char=String.valueOf(check_num).getBytes();
        setHex[16+setHexLen]=(byte)(check_num>>8);
        setHex[17+setHexLen]=(byte)check_num;
        setHex[18+setHexLen]=0x13;
        setHex[19+setHexLen]=0x14;
        return  setHex;
    }

    public String Object_to_xml(List<Contents> data )
    {
        String send_data=
                "<datas>\n" ;
                        String item="";
                        for(int i=0;i<data.size();i++)
                        {
                            item=
                                "<item>" +
                                "<sn>"+String.valueOf(i)+"</sn>" +
                                "<target>"+data.get(i).gettarget()+"</target>\n" +
                                "<content>"+data.get(i).getContent()+"</content>\n" +
                                "<name>"+data.get(i).getName()+"</name>\n" +
                                "</item>\n" ;
                            send_data+=item;
                        }
        send_data=send_data+ "</datas>";
                        return send_data;

    }

    public  List<Contents> xml_to_Object(String data) throws DocumentException {


        List<Contents> reader = new ArrayList<>();
        Contents read=new Contents();
        if(data.length()>30)
        {
            Document document ;
            document = DocumentHelper.parseText(data);
            Element rootEle = document.getRootElement();
            List<Element> bookEles = rootEle.elements();
            for (Element i : bookEles
                    ) {

                read.setSn(i.element("sn").getText());
                read.setName(i.element("name").getText());
                read.setContent(i.element("content").getText());
                read.settarget(i.elementText("target"));
                reader.add(read);

            }
            return reader;
        }
        else
        {
            read=Contents_Init();
            read.setContent(data);
            reader.add(read);
            return reader;
        }

    }
    public Contents Contents_Init()
    {
        Contents read=new Contents();
        read.setSn("0");
        read.settarget("127.0.0.1:1");
        read.setContent("");
        read.setName("");
        return read;

    }

    public Tcp_public_data equip_data_init ()
    {
        Tcp_public_data data=new Tcp_public_data();
        data.setBatch(1);
        data.setKind(0);
        data.setKind(3);
        data.setOpen(0);
        data.setSpeed(0);
        data.setClour(0);
        data.content=new String("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n").getBytes();
        return data;
    }
    /**
     * 获取client对象：ip+port
     */
    public String getIPAddrString(ChannelHandlerContext ctx) {
        String socketString = "";
        socketString = ctx.channel().remoteAddress().toString();
        return socketString;
    }

    /**
     * 获取client的ip
     */
    public String getIPString(ChannelHandlerContext ctx) {
        String ipString = "";
        String socketString = ctx.channel().remoteAddress().toString();
        int colonAt = socketString.indexOf(":");
        ipString = socketString.substring(1, colonAt);
        return ipString;
    }
    /**
     * 发来的相关信息,, 写入Equip_data对象，准备存储。
     */
    public Equip_data Object_to_Equip_data(String name ,ChannelHandlerContext ctx)
    {
        Equip_data data=new Equip_data();
        data.setDate(p.getLongData());
        data.setEquip(ctx);
        data.setIP(getIPAddrString(ctx));
        data.setEquip_name(name);
        return  data;

    }
    /**
     * 删除已经连接的设备
     */
    public void Deleat_info(int i)
    {
        p.print_log(" 踢出用户"+equip_list.get(i).getIP()+equip_list.get(i).getEquip_name() ,5);
        equip_list.remove(i);
    }
    /**
     * 写入编号和IP信息
     */
    public Equip_data Write_info(String name,ChannelHandlerContext ctx)
    {
        int i=-1;
        if(!name.isEmpty()) i=name_check_listequip(name);
        if(i>-1){ Deleat_info(i); }//删除相同名字的链接
        i=ip_check_listequip(getIPAddrString(ctx));
        if(i>-1){ Deleat_info(i); }//删除没有名字的链接
        Equip_data eqd= Object_to_Equip_data(name,ctx);
        equip_list.add(eqd);
        p.print_log("写入信息"+eqd.toString()+"成功。",7);
        return  eqd;
    }

    /**
     * 使用ip检查是否注册过
     */
    public  int ip_check_listequip (String ip)
    {
        String oldip="";
        for (int i=0;i< equip_list.size();i++)
        {
            oldip=equip_list.get(i).getIP();
            if (ip.equals(oldip))
            {
                p.print_log("ip查验,该设备已经注册过。",7);
                return i;
            }
        }
        return  -1;
    }
    /**
     * 使用name检查是否注册过
     */
    public  int name_check_listequip (String name)
    {
        String oldip="";
        for (int i=0;i< equip_list.size();i++)
        {
            oldip=equip_list.get(i).getEquip_name();
            if (name.equals(oldip))
            {
                p.print_log("设备名查验,该设备已经注册过。",7);
                return i;
            }
        }
        return  -1;
    }

public ByteBuf tcp_to_bytebuf(ChannelHandlerContext ctx, Tcp_public_data turn_data )
{
    byte[] senddata= json_to_tcp(turn_data);
    ByteBuf encoded = ctx.alloc().buffer(4 * (senddata.length-4));
    encoded.writeBytes(senddata);
    return  encoded;
}
    public void close_tcp(ChannelHandlerContext ctx) {
        ctx.close();
        ctx.disconnect();
    }

}
//    int head;       //头2
//    int batch;      //批次1
//    int kind;       //种类，1
//    int open;       //开关1
//    int speed;      //速度2
//    int clour;      //颜色6
//    int lenth;      //长度2
//    String content; //内容
//    int check;      //校验2
//    int tail;       //结尾1